﻿using KPIS.GERP.Models;
using KPIS.GERP.Models.Class;
using KPIS.GERP.Models.ICM;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Linq.Dynamic;
using System.Linq.Expressions;
using System.Runtime.Serialization;
using System.ServiceModel;
using System.Text;
using System.Data;
using System.Data.Entity;
using System.Web.Mvc;
using KPIS.GERP.Models.SYS;
namespace KPIS.GERP.WCF.GIMS
{
    [ServiceContract]
    public interface IDeliveryNoteItemService
    {

        #region SelectDeliveryNoteItem
        [OperationContract]
        IEnumerable<DeliveryNoteItem> SelectDeliveryNoteItem(DeliveryNoteItem criticalmodel = null, List<string> includeSubObjectString = null);
        #endregion
        #region SelectDeliveryNotePenalty
        [OperationContract]
        IEnumerable<DeliveryNotePenalty> SelectDeliveryNotePenalty(DeliveryNotePenalty criticalmodel = null, List<string> includeSubObjectString = null);
        #endregion
        #region UpdateDeliveryNoteItem
        [OperationContract]
        void Update(DeliveryNoteItem model, int updateByUserId);
        #endregion
        #region InsertDeliveryNoteItem
        [OperationContract]
        int Insert(DeliveryNoteItem model, int createByUserId);
        #endregion
        #region UpdateDeliveryNotePenalty
        [OperationContract]
        void UpdateDeliveryNotePenalty(DeliveryNotePenalty model, int updateByUserId);
        #endregion
        #region InsertDeliveryNotePenalty
        [OperationContract]
        int InsertDeliveryNotePenalty(DeliveryNotePenalty model,int createByUserId);
        #endregion

        
        #region DeleteDeliveryNotePenalty
        [OperationContract]
        void DeleteDeliveryNotePenalty(int id, int deleteByUserId);
        #endregion

        #region SelectPurchaseOrderPenalty

        [OperationContract]
        IEnumerable<PurchaseOrderPenalty> SelectPurchaseOrderPenalty(PurchaseOrderPenalty criticalmodel = null, List<string> includeSubObjectString = null);
        #endregion
      
    }

    [ServiceErrorBehavior(typeof(ElmahErrorHandler))]

    public class DeliveryNoteItemService : IDeliveryNoteItemService
    {
        #region SelectDeliveryNoteItem
        public IEnumerable<DeliveryNoteItem> SelectDeliveryNoteItem(DeliveryNoteItem criticalmodel = null, List<string> includeSubObjectString = null)
        {
            try
            {
                using (var context = new GERPContext(false))
                {
                    IQueryable<DeliveryNoteItem> query = context.DeliveryNoteItems;

                    if (includeSubObjectString != null)
                    {
                        query = includeSubObjectString.Aggregate(query, (current, includePath) => current.Include(includePath));
                    }

                    List<DeliveryNoteItem> data = new List<DeliveryNoteItem>();
                    if (criticalmodel != null)
                    {
                        object[] param;
                        // problem about record status = null will not return
                        string tempRecordStatus = criticalmodel.RecordStatus;
                        if (criticalmodel.RecordStatus != null)
                        {
                            criticalmodel.RecordStatus = null;
                        }
                        query = query.Where(KPIS.GERP.Models.Class.Utility.GenerateWhereString(criticalmodel, out param) , param);
                        data = query.ToList();
                        if (tempRecordStatus != null)
                        {
                            if (tempRecordStatus.Contains("!"))
                            {
                                tempRecordStatus = tempRecordStatus.Replace("!", "");
                                data = data.Where(o => o.RecordStatus != tempRecordStatus).ToList();
                            }
                            else
                            {
                                data = data.Where(o => o.RecordStatus == tempRecordStatus).ToList();
                            }
                        }
                    }

                    


                    return data;
                }
            }
            catch (Exception ex)
            {
                throw ex;
            }
        }

        #endregion

       #region SelectPurchaseOrderPenalty
       public IEnumerable<PurchaseOrderPenalty> SelectPurchaseOrderPenalty(PurchaseOrderPenalty criticalmodel = null, List<string> includeSubObjectString = null)
    {

   try
            {
                using (var context = new GERPContext(false))
                {
                    IQueryable<PurchaseOrderPenalty> query = context.PurchaseorderPenalties;

                    if (includeSubObjectString != null)
                    {
                        query = includeSubObjectString.Aggregate(query, (current, includePath) => current.Include(includePath));
                    }

                   if (criticalmodel != null)
                    {
                        object[] param;
                        query = query.Where(KPIS.GERP.Models.Class.Utility.GenerateWhereString(criticalmodel, out param), param);
                    }
                    
                    var data = query.ToList();
                    
                   


                    return data;
                }
            }
            catch (Exception ex)
            {
                throw ex;
            }
        }

        #endregion

        #region SelectdeliveryNotePenalty
        public IEnumerable<DeliveryNotePenalty> SelectDeliveryNotePenalty(DeliveryNotePenalty criticalmodel = null, List<string> includeSubObjectString = null)
        {
            
            try
            {
                using (var context = new GERPContext(false))
                {
                    IQueryable<DeliveryNotePenalty> query = context.DeliveryNotePenalties;

                    if (includeSubObjectString != null)
                    {
                        query = includeSubObjectString.Aggregate(query, (current, includePath) => current.Include(includePath));
                    }

                   if (criticalmodel != null)
                    {
                        object[] param;
                        query = query.Where(KPIS.GERP.Models.Class.Utility.GenerateWhereString(criticalmodel, out param), param);
                    }
                    
                    var data = query.ToList();
                    
                   


                    return data;
                }
            }
            catch (Exception ex)
            {
                throw ex;
            }
        }

          
        #endregion


       

        #region UpdateDeliveryNoteItem
        public void Update(DeliveryNoteItem model, int updateByUserId)
        {
            try
            {
                using (var context = new GERPContext())
                {
                    context.Entry(model).State = EntityState.Modified;
                    model.UpdatedBy = updateByUserId;
                    model.UpdatedWhen = DateTime.Now;
                    if (model.DeliveryNote != null && string.IsNullOrWhiteSpace(model.DeliveryNote.Code))
                    {
                        throw new Exception("Dn code null 1");
                    }
                    context.SaveChanges();
                }
            }
            catch(Exception ex)
            {
                throw ex;
            }
        }
        #endregion

        #region InsertDeliveryNoteItem
        public int Insert(DeliveryNoteItem model, int createByUserId)
        {
            try
            {
                using (var context = new GERPContext())
                {
                    

                    model.RecordStatus = RecordStatus.WaitStatus;
                    //model.CreatedBy = createdByUserID;
                    model.CreatedWhen = DateTime.Now;
                    if (model.DeliveryNote != null && string.IsNullOrWhiteSpace(model.DeliveryNote.Code))
                    {
                        throw new Exception("Dn code null 1");
                    }
                    context.DeliveryNoteItems.Add(model);
                    context.SaveChanges();

                    return model.DnItemId;
                }
            }
            catch (Exception ex)
            {
                throw ex;
            }
        }
        #endregion

        #region UpdateDeliveryNotePenalty
        public void UpdateDeliveryNotePenalty(DeliveryNotePenalty model, int updateByUserId)
        {
            try
            {
                using (var context = new GERPContext())
                {
                    context.Entry(model).State = EntityState.Modified;
                    model.UpdatedBy = updateByUserId;
                    model.UpdatedWhen = DateTime.Now;
                    if (model.DeliveryNote != null && string.IsNullOrWhiteSpace(model.DeliveryNote.Code))
                    {
                        throw new Exception("no dn 14");
                    }
                    context.SaveChanges();
                }
            }
            catch (Exception ex)
            {
                throw ex;
            }
        }
        #endregion

        #region InsertDeliveryNotePenalty
        public int InsertDeliveryNotePenalty(DeliveryNotePenalty model, int createByUserId)
        {
            try
            {
                 
                using (var context = new GERPContext())

                {
                   
                   // model.PenaltyAmount = PoPen.PenaltyRate *1;
                    model.CreatedWhen = DateTime.Now;
                    model.CreatedBy = createByUserId;
                    if (model.DeliveryNote != null && string.IsNullOrWhiteSpace(model.DeliveryNote.Code))
                    {
                        throw new Exception("No dn id 12");
                    }
                    context.DeliveryNotePenalties.Add(model);
                    context.SaveChanges();

                    return model.DnPenId;
                }
            }
            catch (Exception ex)
            {
                throw ex;
            }
        }
        #endregion

        #region DeleteDeliveryNotePenalty
        public void DeleteDeliveryNotePenalty(int id, int deleteByUserId)
        {
            try
            {
                using (var context = new GERPContext())
                {
                    var modelToDelete = context.DeliveryNotePenalties.Find(id);
                    if (modelToDelete == null) return;

                    if (modelToDelete.DeliveryNote != null && string.IsNullOrWhiteSpace(modelToDelete.DeliveryNote.Code))
                    {
                        throw new Exception("Dn code null 16");
                    }
                    context.Entry(modelToDelete).State = EntityState.Deleted;
                    context.SaveChanges();
                }
            }
            catch (Exception ex)
            {

                throw ex;
            }

        }
        #endregion
    }
}